package com.yyfax.common.recyclerview.adapter;

import android.support.v7.widget.RecyclerView;
import android.view.View;
import android.view.ViewGroup;
import com.yyfax.common.recyclerview.base.ItemViewDelegate;
import com.yyfax.common.recyclerview.base.ItemViewDelegateManager;
import com.yyfax.common.recyclerview.base.ViewHolder;

import java.util.Collection;
import java.util.ArrayList;
import java.util.List;

/**
 * Created by zhy on 16/4/9.
 * 多类型adapter
 */
public class MultiItemTypeAdapter<T> extends RecyclerView.Adapter<ViewHolder> {
	private List<T> mData = new ArrayList<>();

	private ItemViewDelegateManager mItemViewDelegateManager;
	private OnItemClickListener mOnItemClickListener;

	MultiItemTypeAdapter(List<T> datas , ItemViewDelegateManager itemViewDelegateManager) {
		if (datas != null && datas.size() != 0)
			mData.addAll(datas);
		mItemViewDelegateManager = itemViewDelegateManager;
	}

	/**
	 * Return the view type of the item at <code>position</code> for the purposes
	 * of view recycling.
	 * <p/>
	 * <p>The default implementation of this method returns 0, making the assumption of
	 * a single view type for the adapter. Unlike ListView adapters, types need not
	 * be contiguous. Consider using id resources to uniquely identify item view types.
	 *
	 * @param position position to query
	 * @return integer value identifying the type of the view needed to represent the item at
	 * <code>position</code>. Type codes need not be contiguous.
	 */
	@Override
	public int getItemViewType(int position) {
		if (!useItemViewDelegateManager())
			return super.getItemViewType(position);
		return mItemViewDelegateManager.getItemViewType(mData.get(position), position);
	}

	@Override
	public ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
		ItemViewDelegate itemViewDelegate = mItemViewDelegateManager.getItemViewDelegate(viewType);
		int layoutId = itemViewDelegate.getItemViewLayoutId();
		ViewHolder holder = ViewHolder.createViewHolder(parent.getContext(), parent, layoutId);
		onViewHolderCreated(holder, holder.getConvertView());
		setListener(parent, holder, viewType);
		return holder;
	}

	private void onViewHolderCreated(ViewHolder holder, View itemView) {
	}

	public void convert(ViewHolder holder, T t) {
		mItemViewDelegateManager.convert(holder, t, holder.getAdapterPosition());
	}

	private boolean isEnabled(int viewType) {
		return true;//todo
	}

	private void setListener(final ViewGroup parent, final ViewHolder viewHolder, final int viewType) {
		if (!isEnabled(viewType))
			return;

		viewHolder.getConvertView().setOnClickListener(new View.OnClickListener() {
			@Override
			public void onClick(View v) {
				if (mOnItemClickListener != null) {
					int position = viewHolder.getAdapterPosition();
					mOnItemClickListener.onItemClick(v, viewHolder, position, viewType);
				}
			}
		});

		viewHolder.getConvertView().setOnLongClickListener(new View.OnLongClickListener() {
			@Override
			public boolean onLongClick(View v) {
				if (mOnItemClickListener != null) {
					int position = viewHolder.getAdapterPosition();
					return mOnItemClickListener.onItemLongClick(v, viewHolder, position, viewType);
				}
				return false;
			}
		});
	}

	@Override
	public void onBindViewHolder(ViewHolder holder, int position) {
		convert(holder, mData.get(position));
	}

	@Override
	public int getItemCount() {
		return mData.size();
	}

	public List<T> getData() {
		return mData;
	}

	public MultiItemTypeAdapter addItemViewDelegate(ItemViewDelegate<T> itemViewDelegate) {
		mItemViewDelegateManager.addDelegate(itemViewDelegate);
		return this;
	}

	public MultiItemTypeAdapter addItemViewDelegate(int viewType, ItemViewDelegate<T> itemViewDelegate) {
		mItemViewDelegateManager.addDelegate(viewType, itemViewDelegate);
		return this;
	}

	private boolean useItemViewDelegateManager() {
		return mItemViewDelegateManager.getItemViewDelegateCount() > 0;
	}

	public interface OnItemClickListener {
		void onItemClick(View view, ViewHolder holder, int position, int viewType);

		boolean onItemLongClick(View view, ViewHolder holder, int position, int viewType);
	}

	public void setOnItemClickListener(OnItemClickListener onItemClickListener) {
		this.mOnItemClickListener = onItemClickListener;
	}

	public void addData(T data) {
		if (data != null) {
			mData.add(data);
		}
		notifyDataSetChanged();
	}

	public void addData(Collection<T> data) {
		if (data != null) {
			mData.addAll(data);
		}
		notifyDataSetChanged();
	}

	public void addData(int position, T obj) {
		mData.add(position, obj);
		notifyDataSetChanged();
	}

	public void addData(int index, Collection<T> data) {
		if (data != null) {
			mData.addAll(index, data);
		}
		notifyDataSetChanged();
	}

	public void setData(int position, T data) {
		if (data != null) {
			mData.set(position, data);
		}
		notifyDataSetChanged();
	}

	public void remove(Collection<T> data) {
		if (data != null) {
			mData.removeAll(data);
		}
		notifyDataSetChanged();
	}

	public void remove(int position) {
		mData.remove(position);
		notifyDataSetChanged();
	}

	public void remove(T data) {
		if (data != null) {
			mData.remove(data);
		}
		notifyDataSetChanged();
	}

	public void removeAll() {
		if (mData != null) {
			mData.clear();
		}
		notifyDataSetChanged();
	}

	public boolean isEmpty() {
		return null == mData || mData.size() == 0;
	}

	public List<T> subData(int index, int count) {
		return mData.subList(index, index + count);
	}

	public List<T> getDataSet() {
		return mData;
	}

	public int getCount() {
		return null == mData ? 0 : mData.size();
	}
}
